import 'package:flutter/material.dart';

class Product {
  const Product({required this.name});

  final String name;
}

typedef CartChangedCallback = Function(Product product, bool inCart);

class ShoppingListItem extends StatelessWidget {
  ShoppingListItem({
    required this.product,
    required this.inCart,
    required this.onCartChanged,
  }) : super(key: ObjectKey(product));

  final Product product;
  final bool inCart;
  final CartChangedCallback onCartChanged;

  Color _getColor(BuildContext context) {
    return inCart ? Colors.black54 : Theme.of(context).primaryColor;
  }

  TextStyle ? _getTextStyle(BuildContext context) {
    if (!inCart) return null;

    return const TextStyle(color: Colors.black54, decoration: TextDecoration.lineThrough);
  }

  @override
  Widget build(BuildContext context) {
    return ListTile(
      onTap: () {
        onCartChanged(product, inCart);
      },
      leading: CircleAvatar(backgroundColor: _getColor(context), child: Text(product.name[0]),),
      title: Text(
        product.name,
        style: _getTextStyle(context),
      ),
    );
  }
}

// 继承自statefulWidget，意味着这个widget存储了可变状态，
// 当ShoppingList首次插入到widget树中时，会调用createState()函数来创建_ShoppingListState的新实例，以与树中的该位置相关联
// State的子类，通常以下划线开头进行命名，表示他们的实现细节是私有的
// 当widget的父widget重建时，父widget会创建一个ShoppingList实例，但是框架会复用之前的_ShoppingListState，而不会重新调用createState生成
class ShoppingList extends StatefulWidget {
  const ShoppingList({
    required this.products,
    Key ? key
  }) : super(key: key);

  final List<Product> products;

  @override
  _ShoppingListState createState() => _ShoppingListState();
}

class _ShoppingListState extends State<ShoppingList> {
  final _shoppingCart = <Product>{};

  // 当处理onCartChanged回调函数时，_ShoppingListState会通过增加/删除_shoppingCart的产品改变其内部的状态
  void _handleCartChanged(Product product, bool inCart) {
    // 为了通知框架他改变了内部状态，需要调用setState()，此时会在下次应用需要更新时重写构建这个内部状态，否则不会进行状态的更新
    setState(() {
      if (!inCart) {
        _shoppingCart.add(product);
      } else {
        _shoppingCart.remove(product);
      }
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(title: const Text('Shopping List'),),
      body: ListView(
        padding: const EdgeInsets.symmetric(vertical: 8.0),
        // _ShoppingListState可以使用他的widget属性访问父级widget（当前ShoppingList）的属性
        // 父组件重建一个新的ShoppingList时，_ShoppingListState会同步更新widget属性（同步更新父级属性）
        // 若希望widget属性更改时收到通知，则可以重写didUpdateWidget()函数，该函数将oldWidget作为参数传递，以便将oldWidget和当前的widget进行比较
        children: widget.products.map((Product product) {
          return ShoppingListItem(product: product, inCart: _shoppingCart.contains(product), onCartChanged: _handleCartChanged);
        }).toList(),
      ),
    );
  }
}

class Q0107 extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'shopping app',
      home: ShoppingList(products: [
        Product(name: 'Eggs'),
        Product(name: 'Flour'),
        Product(name: 'Chocolate chips')
      ],)
    );
  }
}